#!/bin/bash

#----------------------------------------------------
# File: file.sh
# Contents: linux file system
# Date: 19-5-3
#----------------------------------------------------

#---------------------------------------------------------------------------------------------------
# Linux中实现的自主访问控制(DAC)机制主要包括基础的 UGO+RWX 和加强的 ACL(Access Control List).
#---------------------------------------------------------------------------------------------------

#---------------------------------------------------------------------------------------------------
# UGO+RWX 相关
#
# 该机制的思想是通过对用户(组)及其所属进程对文件和目录的访问赋予一定的权限, 来实现基本的权限管理与访问控制.
#
# Linux为每个文件都分配了一个文件所有者, 称为文件主, 并赋予文件主惟一的注册名. 对文件的控制取决于文件主或
# 超级用户(root). 文件或目录的创建者对创建的文件或目录拥有特别使用权.
#
# 文件的所有关系是可以改变的, 可以将文件或目录的所有权转让给其它用户, 但只有文件主或root用户才有权改变文件
# 的所有关系. 文件的所有权的标志是用户ID(UID), 这正是DAC机制的核心概念.
#
#
# UGO+RWX 表示
#
# Linux系统中的每个文件和目录(客体)都有相应的访问权限, 通过其访问权限可以确定谁(主体)可以通过何种方式对文
# 件/目录进行访问和操作.
#
# 文件/目录(客体)的访问权限分为三种: 读(r), 写(w), 和 执行(x). 该机制限制三种不同的主体: 文件所有者(u),
# 同组用户(g) 和 其他用户(o).
#
# 每个文件或目录的访问权限都有三组, 每组用三位表示，分别为文件属主的读、写和执行三种权限.
#
# 权限列共有 10 个字符, 第一个字符为文件类型, 后面九个分为三组: 第一组为 U(User), 即文件属主对应的权限;
# 第二组为 G(Group), 即同组用户对应的权限; 第三组为 O(Others), 即其他用户对应的权限.
#
# 文件类型: - 代表普通文件, l 代表链接文件, d代表目录文件, s 代表数据接口文件(用在网络上的数据承接),  b
# 代表区块设备档(存储数据, 以提供系统随机存取的接口设备, 比如硬盘,软盘等), c 代表字符设备文件(串行端口的接
# 口设备, 比如键盘, 鼠标等), p 代表数据输送文件(FIFO是一种特殊的文件类型, 主要目的是解决多个程序同时存取一
# 个文件所造成的错误问题)
#
# 文件权限说明:
#
# +-----------+-----------------------------+-------------------------------------------------+
# |           |           file              |                    directory                    |
# +-----------+-----------------------------+-------------------------------------------------+
# |    R      |  读取文件内容                 | 读包含在目录中的文件名称                            |
# +-----------+-----------------------------+-------------------------------------------------+
# |    W      |  对文件内容进行编辑            | 可以写信息到目录中, 即可以创建,删除,移动文件操作        |
# +-----------+-----------------------------+-------------------------------------------------+
# |    X      |  作为执行文件执行              | 可以进入目录;可以搜索(能用该目录名称作为路径名去访问它所包|
# |           |                             | 含的的文件和子目录)                                |
# +-----------+-----------------------------+-------------------------------------------------+
#
# 案例:
# 1.对目录必须有 x 权限才能 cd 进入到目录, 必须有 rx 权限才能使用 ls 列出目录清单
#---------------------------------------------------------------------------------------------------


#---------------------------------------------------------------------------------------------------
# chmod
#
#   chmod命令可以修改文件或目录的权限, 但有两种方式来修改, 一种是字母权限设定法, 另一种是数字权限设定法. 用字母
# 权限设定法时, 该命令的格式通常是:
#
# chmod [who] [+|-|=] [mode] [file/dir]
# 其中, 操作对象 who 表示将权限赋予的主体; [+|-|=] 是权限的操作符; [mode]是权限
#
# who 可以是下列字母中的单个或多个的组合:
#   - u: 表示用户(user), 文件属主
#   - g: 表示同组用户(group), 文件属主在同一用户组的用户
#   - o: 表示其他用户(other)
#   - a: 表示所有用户(all), 系统默认值
#
# mode 可以是下列字母的任意组合:
#   - r: 可读
#   - w: 可写
#   - x: 可执行
#   - s: 在文件执行时, 把进程的属主或组ID置为该文件的文件属主. 方式 `u+s` 设置文件的用户ID位, `g+s` 设置组ID位
#   - t: 文件的粘滞位
#   - u: 与文件属主拥有同样的权限
#   - g: 与文件属主同组用户拥有同样的权限
#   - o: 与其他用户拥有同样的权限
#
# t, 粘滞位:
#   t是针对others来设置的. SBIT(Sticky Bit) 目前只针对目录有效, 对于目录的作用是: 当前用户在该目录下建立文件或
# 者目录时, 只有用户自己和root才有权限删除所创建的目录或文件.
#   最具代表的就是/tmp目录, 任何人都可以在/tmp内增加,修改文件(因为权限是rwx), 但仅有该文件/目录的建立者与root才
# 能够删除其目录或文件.
#
# s, 设置ID
#   SUID, 当s标志出现在文件所有者的x权限上时, 此时称为SUID(Set UID)
#   ①, SUID权限仅对二进制程序有效;
#   ②, 执行者对于该程序需要具有x的可执行权限;
#   ③, 本权限仅在执行该程序的过程中有效(run-time);
#   ④, 执行者将具有该程序所有者(owner)的权限;
#
#   SUID的目的是: 让本来没有相应权限的用户运行这个程序时, 可以访问它没有权限访问的资源. passwd 命令就是一个案例.
#
#   SGID, 当s标志出现在文件所属用户组的x权限上时, 此时称为SGID(Set GID)
#   ①, SGID 对二进制程序有用;
#   ②, 程序执行者对于该程序来说, 需具备x的权限
#   ③, SGID 主要用在目录上;
#
#   SGID目的: 任何用户在此目录下创建的文件都具有和该目录所属的组相同的组.
#
#
# 操作符号:
#   +: 添加某权限
#   -: 取消某权限
#   =: 覆盖原权限
#---------------------------------------------------------------------------------------------------


#---------------------------------------------------------------------------------------------------
# ACL
#
#   在Linux当中, 最基本的文件管控是 UGO+RWX, 也就是上述提到的方案. 但是这种方案存在很大的问题是, 对于 other 的
# 定义过于广泛, 以至于很难把权限限定于一个不属于文件 owner和group 的用户上. ACL(访问控制列表)就是用来解决此问题的.
#
#   相关命令: getfacl setfacl chacl
#
#   ACL 是由一系列的 Access Entry 所组成的. 每一条 Access Entry 定义了特定的类别可以对文件拥有的操作权限. Access
# Entry 有三个组成部分: Entry tag type, qualifier(optional), permission
#
# Entry tag type类型:
#   - ACL_USER_OBJ: 相当于Linux里权限位 u
#   - ACL_USER: 定义了额外的用户可以对此文件拥有的权限
#   - ACL_GROUP_OBJ: 相当于Linux里权限位 g
#   - ACL_GROUP: 定义了额外的组可以对此文件拥有的权限
#   - ACL_MASK: 定义了ACL_USER, ACL_GROUP_OBJ 和 ACL_GROUP 的最大权限
#   - ACL_OTHER: 相当于LInux里权限位 o
#
#
# 案例:
#   使用getfacl 获取文件ACL的权限
# # file: test.txt
# # owner: leonard
# # group: admin
# user::rw-
# user:john:rw-
# group::rw-
# group:dev:r--
# mask::rw-
# other::r--
#
# 前面三个以#开头的定义了文件名,file,owner和group, 这些只是辅助信息, 没有太大的作用, 可以用 --omit-header参数来
# 省略掉.
#
# user::rw- : 定义了ACL_USER_OBJ,说明file owner拥有读写权限;
# user:john:rw- : 定义了ACL_USER,这样用户john就拥有了对文件的读写权限,实现了我们一开始要达到的目的;
# group::rw- : 定义了ACL_GROUP_OBJ,说明文件的group拥有读写权限;
# group:dev:r– : 定义了ACL_GROUP,使得dev组拥有了对文件的读权限;
# mask::rw- : 定义了ACL_MASK的权限为读和写;
# other::r– : 定义了ACL_OTHER的权限为读。
#
#---------------------------------------------------------------------------------------------------

#---------------------------------------------------------------------------------------------------
# chattr 和 lsattr
#
#---------------------------------------------------------------------------------------------------
